/*
 * To change this template, choose Tools | Templates
 * and open the template in the editor.
 */

package View.ClusterizationPanel;

import Controller.StarClusterController;
import Model.*;
import View.StarClusterMainWindow;
import javax.swing.*;
import java.awt.*;
import java.awt.event.*;
import java.util.ArrayList;
/**
 *
 * @author vf
 */
public class ClusterizationWindow extends JFrame implements ComponentListener{

    /*
    private View.ClusterizationPanel.CentroidTable centroidTable1;
    private javax.swing.JScrollPane jScrollPane1;
    private javax.swing.JSplitPane jSplitPane1;
    private javax.swing.JSplitPane jSplitPane2;
    private View.ClusterizationPanel.OptionsPanel optionsPanel1;
    private View.ClusterizationPanel.View3DPanel view3DPanel1;
     * */

    String options;
    private DataSet dataSet;
    private Clusterization currentClusterization;
    private CentroidTable centroidTable1;
    private OptionsPanel optionsPanel1;
    private View3DPanel view3DPanel1;
    JScrollPane centroidTableContainer;
    JSplitPane fullWindow;
    JSplitPane viewAndCentroidTable;
    private Distance[] distances;
    private boolean sceneIsCompiled;
    private int optionsPanelWidth;
    private int currentClusterizationIndex;
    private StarClusterMainWindow mainWindow;
    private StarClusterController dataController;
    
    public ClusterizationWindow (StarClusterMainWindow mainWin,StarClusterController dataController,final DataSet dataSet, String options){
        this.mainWindow=mainWin;
        this.dataController=dataController;
        this.options=options;
        this.dataSet=dataSet;
        sceneIsCompiled = false;
        distances = Distance.values();
        currentClusterizationIndex = -1;
        this.setLayout(new BorderLayout());
        setTitle("Clusterization view");
        setLocation(500, 100);
        //setMinimumSize(new Dimension(700,480));
        addComponentListener(this);
        
        addWindowListener(
            new WindowAdapter(){
                public void windowClosing(WindowEvent e) {
                    mainWindow.removeClusterizationWindow((ClusterizationWindow)e.getWindow());
                    dataSet.deleteClusterization(currentClusterizationIndex);
                    closeWin();
                }
            }
        );

        //initComponents();

        
        centroidTable1=new CentroidTable();
        centroidTable1.setParent(this);
        centroidTableContainer=new JScrollPane();
        centroidTableContainer.setViewportView(centroidTable1);
        centroidTableContainer.setMaximumSize(centroidTable1.getMaximumSize());
        view3DPanel1 = new View3DPanel();
        view3DPanel1.setParent(this);
        //view3DPanel1.setSize(640,480);
        //centroidTableContainer.setSize(640,0);

        viewAndCentroidTable=new JSplitPane(JSplitPane.VERTICAL_SPLIT,view3DPanel1,centroidTableContainer);
        viewAndCentroidTable.setResizeWeight(1.0);
        viewAndCentroidTable.setContinuousLayout(true);
        viewAndCentroidTable.setDividerSize(5);


        //viewAndCentroidTable.add(view3DPanel, BorderLayout.CENTER);
        //viewAndCentroidTable.add(centroidTable, BorderLayout.SOUTH);

        //this.add(viewAndCentroidTable,BorderLayout.CENTER);
        //this.add(optionPanel, BorderLayout.EAST);

        if (options.equals("kmeans")){
            optionsPanel1 = new KmeansOptionsPanel();
            optionsPanel1.setParent(this);
        }
        else if (options.equals("hierarchical")){
            optionsPanel1 = new HierarchicalOptionsPanel();
            optionsPanel1.setParent(this);
        }
        else if (options.equals("custom")){
            optionsPanel1 = new CustomOptionsPanel();
            optionsPanel1.setParent(this);
        }
        //this.add(optionsPanel, BorderLayout.EAST);
        fullWindow=new JSplitPane(JSplitPane.HORIZONTAL_SPLIT,viewAndCentroidTable,optionsPanel1);
        fullWindow.setResizeWeight(1.0);
        fullWindow.setContinuousLayout(true);
        this.add(fullWindow, BorderLayout.CENTER);
        //view3DPanel1.setSize(640,480);
        //centroidTableContainer.setSize(640,60);
        fullWindow.setDividerSize(5);
        
        //viewAndCentroidTable.setDividerLocation(550);
        //view3DPanel1.setSize(640,635);
        optionsPanel1.setSize(200,640);
        //centroidTable1.setMinimumSize(new Dimension(0,0));
        centroidTable1.setSize(640,0);
        //centroidTableContainer.setMinimumSize(new Dimension(0,0));
        centroidTableContainer.setSize(640,0);

        viewAndCentroidTable.setSize(640,550);
        
        centroidTableContainer.setVisible(false);
        centroidTableContainer.setMinimumSize(new Dimension(150,100));
        
        fullWindow.setSize(845,640);
        fullWindow.setMaximumSize(new Dimension(845,640));
        this.setVisible(true);
        this.setSize(845,640);
        this.setMaximumSize(new Dimension(845,640));
        //pack();

    }

    private void compute3DCoords(){
        Preprocessor a=new Preprocessor(dataSet);
        a.set3DCoords(currentClusterization);

    }
    
    private void update3DView(){
        componentResized(new ComponentEvent(this, 0));
        compute3DCoords();
        if (!sceneIsCompiled)
        {
            view3DPanel1.addSceneView();
            sceneIsCompiled = true;
        }
        else
            view3DPanel1.compileScene();
    }

    public void updateCentroidSelection(boolean[] centroidSelected){
        view3DPanel1.updateCentroidSelection(centroidSelected);
    }

    public void updateActionSelection(int[] selectedActions){
        view3DPanel1.updateActionSelection(selectedActions);
    }
    
    public void createKmeans(String name) {
        if (currentClusterizationIndex>=0)
            dataSet.deleteClusterization(currentClusterizationIndex);
        int NbClusters = optionsPanel1.getNumberOfClusters();
        boolean normalize = optionsPanel1.getNormalisationValue();
        Distance dist = Distance.valueOf(optionsPanel1.getDistanceValue());
        ArrayList<Cluster> clusList=new ArrayList<Cluster>();
        for(int i=0;i<NbClusters;i++){
            Cluster clus=new Cluster(dataSet,optionsPanel1.getClusterName(i),optionsPanel1.getClusterColor(i));
            clusList.add(clus);
        }
        ArrayList<Weight> weightList=new ArrayList<Weight>();
        for(int i=0;i<getAttributeNbr();i++){
            Weight weight;
            if(optionsPanel1.getAttributeWeight(i)>0){
                weight=new Weight(dataSet.getAttribute(i),optionsPanel1.getAttributeWeight(i));
                weightList.add(weight);
            }
        }
        KmeansOptions kOpt=new KmeansOptions(dataSet,name,clusList,dist,weightList,normalize);
        dataSet.addClusterization(kOpt);
        System.out.println("done creating new clusterization");
        currentClusterizationIndex = dataSet.getClusterizationNbr()-1;
        currentClusterization = dataSet.getClusterization(currentClusterizationIndex);
        updateComponents();
    }

    public void createHierarchical (String name) {
        if (currentClusterizationIndex>=0)
            dataSet.deleteClusterization(currentClusterizationIndex);
        int NbClusters = optionsPanel1.getNumberOfClusters();
        boolean normalize = optionsPanel1.getNormalisationValue();
        Distance dist = Distance.valueOf(optionsPanel1.getDistanceValue());
        ArrayList<Cluster> clusList=new ArrayList<Cluster>();
        for(int i=0;i<NbClusters;i++){
            Cluster clus=new Cluster(dataSet,optionsPanel1.getClusterName(i),optionsPanel1.getClusterColor(i));
            clusList.add(clus);
        }
        ArrayList<Weight> weightList=new ArrayList<Weight>();
        for(int i=0;i<getAttributeNbr();i++){
            Weight weight;
            if(optionsPanel1.getAttributeWeight(i)>0){
                weight=new Weight(dataSet.getAttribute(i),optionsPanel1.getAttributeWeight(i));
                weightList.add(weight);
            }
        }
        HierarchicalOptions hOpt=new HierarchicalOptions(dataSet,name,clusList,dist,weightList,normalize);
        dataSet.addClusterization(hOpt);
        System.out.println("done creating new clusterization");
        currentClusterizationIndex = dataSet.getClusterizationNbr()-1;
        currentClusterization = dataSet.getClusterization(currentClusterizationIndex);
        updateComponents();
    }

    public void createCustom (String name){
        if (currentClusterizationIndex>=0)
            dataSet.deleteClusterization(currentClusterizationIndex);
        int NbClusters = optionsPanel1.getNumberOfClusters();
        ArrayList<Integer>[] actionList=new ArrayList[NbClusters];
        for(int i=0;i<NbClusters;i++)
            actionList[i] = new ArrayList<Integer>();

        ArrayList<Cluster> clusList=new ArrayList<Cluster>();
        for(int i=0;i<NbClusters;i++){
            Cluster clus=new Cluster(dataSet,optionsPanel1.getClusterName(i),optionsPanel1.getClusterColor(i));
            clusList.add(clus);
            for (int j=0;j < ((CustomOptionsPanel)optionsPanel1).getActionsCountAssignedTo(i);j++)
                actionList[i].add(((CustomOptionsPanel)optionsPanel1).getActionAssignedTo(i,j));
        }
        CustomOptions cOpt=new CustomOptions(dataSet,name,clusList,actionList);
        dataSet.addClusterization(cOpt);
        currentClusterizationIndex = dataSet.getClusterizationNbr()-1;
        currentClusterization = dataSet.getClusterization(currentClusterizationIndex);
        updateComponents();
    }

    public int getNumberOfActions() {
        return dataSet.getActionNbr();
    }

    public Color getActionColor(int i) {
        return dataSet.getActionColor(i,currentClusterization);
    }

    public Object getValue(int actionIndex, int clusterIndex) {
        return dataSet.getValue(actionIndex, clusterIndex);
    }

    public float[] getActionsCoords(int i) {
        return dataSet.getActionCoords(i);
    }

    public float[] getClusterCoords(int i) {
        return dataSet.getClusterCoords(currentClusterization,i);
    }

    public String getClusterName(int clusterIndex) {
        return dataSet.getClusterName(currentClusterization,clusterIndex);
    }

    void setClusterName(int clusterIndex, String name) {
        dataController.setClusterName(currentClusterization,clusterIndex,name);
    }

    public int getNumberOfClusters() {
        if(currentClusterization==null) return 0;
        else return currentClusterization.getClusterNbr();
    }

    public int getAttributeNbr() {
        return dataSet.getAttributeNbr();
    }

    public AttributeType getAttributeType(int attributeIndex) {
        return dataSet.getAttributeType(attributeIndex);
    }

    public int getNumberOfClusterizations() {
        return dataSet.getClusterizationNbr();
    }

    public String getAttributeName(int i) {
        return dataSet.getAttributeName(i);
    }

    public int getNumberOfDistances(){
        return distances.length;
    }

    public String getDistanceType(int i){
        return distances[i].toString();
    }

    public Object getCentroidValue(int index, int attributeIndex) {
        return dataSet.getValue(currentClusterization, index, dataSet.getAttribute(attributeIndex), false);
    }

    public Color getClusterColor(int i) {
        return optionsPanel1.getClusterColor(i);
    }

    public void setClusterName(String name,int clusterIndex) {
        dataSet.setClusterName(currentClusterization,clusterIndex,name);
    }

    private void closeWin(){
        optionsPanel1.closeWin();
        dispose();
    }

    public void componentResized(ComponentEvent e) {
        /*
        int width = this.getWidth();
        int height = this.getHeight();
        optionsPanelWidth = optionsPanel.getMinimumSize().width;
        System.out.println(optionsPanelWidth);
        view3DPanel.newSize(width-optionsPanelWidth, height);
        optionsPanel.newSize(optionsPanelWidth,height);
        optionsPanel.revalidate();
         * */
    }

    public void componentMoved(ComponentEvent e) {
        //throw new UnsupportedOperationException("Not supported yet.");
    }

    public void componentShown(ComponentEvent e) {
        //throw new UnsupportedOperationException("Not supported yet.");
    }

    public void componentHidden(ComponentEvent e) {
        //throw new UnsupportedOperationException("Not supported yet.");
    }

    private void updateComponents() {
        update3DView();
        centroidTable1=new CentroidTable();
        centroidTable1.setParent(this);
        centroidTableContainer.setVisible(true);
        centroidTableContainer.setMinimumSize(new Dimension(150,100));

        //centroidTableContainer.setMaximumSize(centroidTable1.getMaximumSize());
        //centroidTableContainer.setSize(centroidTable1.getMaximumSize());
        //centroidTable1.repaint();
        //this.setSize(fullWindow.getSize());
        //repaint();
        this.setPreferredSize(this.getSize());
        centroidTable1.setSize(view3DPanel1.getWidth(),centroidTable1.getDesiredHeight());
        centroidTable1.setPreferredSize(new Dimension(view3DPanel1.getWidth(),centroidTable1.getDesiredHeight()));
        centroidTableContainer.setSize(view3DPanel1.getWidth(),centroidTable1.getDesiredHeight());
        centroidTableContainer.setPreferredSize(new Dimension(view3DPanel1.getWidth(),centroidTable1.getDesiredHeight()));
        view3DPanel1.setSize(this.getWidth()-5-optionsPanel1.getWidth(),this.getHeight()- viewAndCentroidTable.getDividerSize()- viewAndCentroidTable.getInsets().top-centroidTable1.getDesiredHeight());
        view3DPanel1.setPreferredSize(new Dimension(this.getWidth()-5-optionsPanel1.getWidth(),this.getHeight()- viewAndCentroidTable.getDividerSize()- viewAndCentroidTable.getInsets().top-centroidTable1.getHeight()));
        view3DPanel1.setMinimumSize(new Dimension(150,150));
        viewAndCentroidTable.setDividerLocation(this.getHeight()- viewAndCentroidTable.getDividerSize()- viewAndCentroidTable.getInsets().top-150);

        pack();

        repaint();
    }
/*
    private void initComponents() {

        jSplitPane1 = new javax.swing.JSplitPane();
        jSplitPane2 = new javax.swing.JSplitPane();
        view3DPanel1 = new View.ClusterizationPanel.View3DPanel();
        view3DPanel1.setParent(this);
        jScrollPane1 = new javax.swing.JScrollPane();
        centroidTable1 = new View.ClusterizationPanel.CentroidTable();
        centroidTable1.setParent(this);
         if (options.equals("kmeans")){
            optionsPanel1 = new KmeansOptionsPanel();
            optionsPanel1.setParent(this);
        }
        else if (options.equals("hierarchical"))
            optionsPanel1 = new HierarchicalOptionsPanel(this);

        setDefaultCloseOperation(javax.swing.WindowConstants.EXIT_ON_CLOSE);

        jSplitPane1.setDividerLocation(640);

        jSplitPane2.setDividerLocation(400);
        jSplitPane2.setOrientation(javax.swing.JSplitPane.VERTICAL_SPLIT);

        view3DPanel1.setMinimumSize(new java.awt.Dimension(320, 240));
        view3DPanel1.setPreferredSize(new java.awt.Dimension(640, 480));

        javax.swing.GroupLayout view3DPanel1Layout = new javax.swing.GroupLayout(view3DPanel1);
        view3DPanel1.setLayout(view3DPanel1Layout);
        view3DPanel1Layout.setHorizontalGroup(
            view3DPanel1Layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
            .addGap(0, 640, Short.MAX_VALUE)
        );
        view3DPanel1Layout.setVerticalGroup(
            view3DPanel1Layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
            .addGap(0, 480, Short.MAX_VALUE)
        );

        jSplitPane2.setTopComponent(view3DPanel1);

        centroidTable1.setModel(new javax.swing.table.DefaultTableModel(
            new Object [][] {
                {null, null, null, null},
                {null, null, null, null},
                {null, null, null, null},
                {null, null, null, null}
            },
            new String [] {
                "Title 1", "Title 2", "Title 3", "Title 4"
            }
        ));
        jScrollPane1.setViewportView(centroidTable1);

        jSplitPane2.setRightComponent(jScrollPane1);

        jSplitPane1.setLeftComponent(jSplitPane2);

        javax.swing.GroupLayout kmeansOptionsPanel1Layout = new javax.swing.GroupLayout(optionsPanel1);
        optionsPanel1.setLayout(kmeansOptionsPanel1Layout);
        kmeansOptionsPanel1Layout.setHorizontalGroup(
            kmeansOptionsPanel1Layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
            .addGap(0, 175, Short.MAX_VALUE)
        );
        kmeansOptionsPanel1Layout.setVerticalGroup(
            kmeansOptionsPanel1Layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
            .addGap(0, 517, Short.MAX_VALUE)
        );

        jSplitPane1.setRightComponent(optionsPanel1);

        javax.swing.GroupLayout layout = new javax.swing.GroupLayout(getContentPane());
        getContentPane().setLayout(layout);
        layout.setHorizontalGroup(
            layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
            .addGroup(javax.swing.GroupLayout.Alignment.TRAILING, layout.createSequentialGroup()
                .addContainerGap()
                .addComponent(jSplitPane1, javax.swing.GroupLayout.DEFAULT_SIZE, 824, Short.MAX_VALUE))
        );
        layout.setVerticalGroup(
            layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING)
            .addGroup(layout.createSequentialGroup()
                .addContainerGap()
                .addComponent(jSplitPane1, javax.swing.GroupLayout.PREFERRED_SIZE, 519, javax.swing.GroupLayout.PREFERRED_SIZE)
                .addContainerGap(15, Short.MAX_VALUE))
        );

        pack();
    }
*/


}
